package com.mj.processController;
/**
 * @author cRyann
 * @create 2017-06-05 12:03
 **/

import com.mj.util.ToWeb;
import org.activiti.engine.ProcessEngine;
import org.activiti.engine.RepositoryService;
import org.activiti.engine.RuntimeService;
import org.activiti.engine.TaskService;
import org.activiti.engine.repository.ProcessDefinition;
import org.activiti.engine.runtime.ProcessInstance;
import org.activiti.engine.task.Task;
import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.RestController;

import java.io.InputStream;
import java.util.List;
import java.util.Map;

/**
 * @author cRyann
 * @create 2017-06-05 12:03
 **/
@RestController
public class ProcessEngineCore {
    private Logger logger = Logger.getLogger(this.getClass());

    @Autowired
    ProcessEngine processEngine;
    @Autowired
    RepositoryService repositoryService;
    @Autowired
    RuntimeService runtimeService;
    @Autowired
    TaskService taskService;
    @Autowired
    TaskController taskController;

    @RequestMapping("startProcess/{deploymentId}")
    @ResponseBody
    public Object startInstanceBydDeploymentId(@PathVariable("deploymentId") String deploymentId, Map<String, Object> proMap) {
        ProcessInstance processInstance = null;
//        Model model = repositoryService.createModelQuery().deploymentId(deploymentId).singleResult();
        ProcessDefinition processDefinition = repositoryService.createProcessDefinitionQuery()
                .deploymentId(deploymentId).singleResult();
//        String processInstanceByKey = model.getKey();
        if (proMap != null && proMap.size() > 0) {
            processInstance = runtimeService.startProcessInstanceById(processDefinition.getId(), proMap);
        } else {
            processInstance = runtimeService.startProcessInstanceById(processDefinition.getId());
        }
        return ToWeb.buildResult().refresh();
    }

    /**
     * @param
     * @author cRyann
     * @Description 启动进程（创建新的进程实例）
     **/
    public ProcessInstance startInstanceByKey(String deploymentKey, Map<String, Object> proMap) {
        ProcessInstance processInstance = null;
        if (proMap != null) {
            processInstance = runtimeService.startProcessInstanceByKey(deploymentKey, proMap);
        } else {
            processInstance = runtimeService.startProcessInstanceByKey(deploymentKey);
        }
        logger.info("process start success  key [" + deploymentKey + "]");
        return processInstance;
    }


    @RequestMapping("pauseByDeploymentKey/{processKey}")
    public void pauseByDeploymentKey(@PathVariable("processKey") String processKey) {
        ProcessInstance processInstance = runtimeService.createProcessInstanceQuery()
                .processDefinitionKey(processKey).singleResult();
        runtimeService.suspendProcessInstanceById(processInstance.getId());
        logger.info("process paused success  key [" + processKey + "]");
//        return processInstance;
    }

    /**
     * @param
     * @author cRyann
     * @Description 接收到开工信号
     **/
    @RequestMapping("workStartByDeploymentKey/{processKey}")
    @ResponseBody
    public Object workStartByDeploymentKey(@PathVariable("processKey") String deploymentKey, Map<String, Object> proMap) {
        ProcessInstance processInstance = runtimeService.createProcessInstanceQuery()
                .processDefinitionKey(deploymentKey).singleResult();
        //解挂
//        runtimeService.activateProcessInstanceById(processInstance.getId());
//        logger.info("process resumed success  key [" + deploymentKey + "]");
        Task task = taskService.createTaskQuery()
                .processDefinitionId(processInstance.getProcessDefinitionId())
                .singleResult();
        String processId = task.getProcessInstanceId();
        String targetTaskDefinitionKey = task.getTaskDefinitionKey();
        try {
            taskController.jump(targetTaskDefinitionKey, processId);
        } catch (Exception e) {
            e.printStackTrace();
        }
        logger.debug("process reset success  key [" + deploymentKey + "]");
        return ToWeb.buildResult().refresh();
    }

    //内部调用
    public void workStartByProcessDefinitionId(String processDefinitionId, Map<String, Object> proMap) {
        Task task = taskService.createTaskQuery().processDefinitionId(processDefinitionId).singleResult();
        if (task != null) {
            String processId = task.getProcessInstanceId();
            String targetTaskDefinitionKey = task.getTaskDefinitionKey();
            try {
                taskController.jump(targetTaskDefinitionKey, processId);
            } catch (Exception e) {
                e.printStackTrace();
            }
            logger.debug("process reset success  key [" + processDefinitionId + "]");
        }
    }

    /**
     * @param
     * @author cRyann
     * @Description 接收到完工信号
     **/
    @RequestMapping("workCompleteByDeploymentKey/{processKey}")
    @ResponseBody
    public Object workCompleteByDeploymentKey(@PathVariable("processKey") String processKey, Map<String, Object> proMap) {
        try {
            ProcessDefinition processDefinition = repositoryService.createProcessDefinitionQuery()
                    .processDefinitionKey(processKey).singleResult();
            Task task = taskService.createTaskQuery().processDefinitionId(processDefinition.getId()).singleResult();
            if (proMap != null && proMap.size() > 0) {
                taskService.complete(task.getId(), proMap);
            } else {
                taskService.complete(task.getId());
            }
            //挂起
//            ProcessInstance processInstance = runtimeService.createProcessInstanceQuery()
//                    .processDefinitionKey(processKey).singleResult();
//            runtimeService.suspendProcessInstanceById(processInstance.getId());
//            logger.info("process paused success  key [" + processKey + "]");
        } catch (Exception e) {
            return "false";
        }
        return ToWeb.buildResult().refresh();
    }

    public String workCompleteByProcessDefinitionId(String processDefinitionId, Map<String, Object> proMap) {
        try {
            Task task = taskService.createTaskQuery().processDefinitionId(processDefinitionId).singleResult();
            if (task != null) {
                if (proMap != null && proMap.size() > 0) {
                    taskService.complete(task.getId(), proMap);
                } else {
                    taskService.complete(task.getId());
                }
                return task.getName();
                //挂起
//            ProcessInstance processInstance = runtimeService.createProcessInstanceQuery()
//                    .processDefinitionKey(processKey).singleResult();
//            runtimeService.suspendProcessInstanceById(processInstance.getId());
//            logger.info("process paused success  key [" + processKey + "]");
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

    //
    public boolean isProcessEndByProcessDefinitionId(String processDefinitionId) {
        ProcessInstance pi = runtimeService//表示正在执行的流程实例和执行对象
                .createProcessInstanceQuery()//创建流程实例查询
                .processDefinitionId(processDefinitionId)//使用流程实例ID查询
                .singleResult();

        return pi == null ? true : false;

    }

    public boolean isExistProcessDefinitionId(String definitionKey) {
        ProcessDefinition pi = repositoryService
                .createProcessDefinitionQuery()
                .processDefinitionKey(definitionKey)
                .singleResult();
        return pi != null ? true : false;

    }

    @RequestMapping("viewImage/{deploymentId}")
    public InputStream viewImage(@PathVariable("deploymentId") String deploymentId) throws Exception {
        ProcessDefinition processDefinition = repositoryService.createProcessDefinitionQuery()
                .deploymentId(deploymentId)
                .singleResult();
        String diagramResourceName = processDefinition.getDiagramResourceName();
        InputStream imageStream = repositoryService
                .getResourceAsStream(processDefinition.getDeploymentId(), diagramResourceName);
        return imageStream;
    }

    public boolean existSameKeyDef(String processKey) {
        List<ProcessInstance> list = runtimeService.createProcessInstanceQuery()
                .processDefinitionKey(processKey).list();
        return list.size() > 0 ? true : false;
    }
}
